package com.fqxiny.lease.web.admin.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.fqxiny.lease.common.exception.UpException;
import com.fqxiny.lease.common.result.ResultCodeEnum;
import com.fqxiny.lease.model.entity.*;
import com.fqxiny.lease.model.enums.ItemType;
import com.fqxiny.lease.web.admin.service.*;
import com.fqxiny.lease.web.admin.mapper.ApartmentInfoMapper;
import com.fqxiny.lease.web.admin.vo.apartment.ApartmentDetailVo;
import com.fqxiny.lease.web.admin.vo.apartment.ApartmentItemVo;
import com.fqxiny.lease.web.admin.vo.apartment.ApartmentQueryVo;
import com.fqxiny.lease.web.admin.vo.apartment.ApartmentSubmitVo;

import com.fqxiny.lease.web.admin.vo.graph.GraphVo;
import jakarta.annotation.Resource;
import kotlin.jvm.internal.Lambda;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.ArrayList;
import java.util.List;

/**
* @author 25312
* @description 针对表【apartment_info(公寓信息表)】的数据库操作Service实现
* @createDate 2025-03-25 19:55:24
*/
@Service
public class ApartmentInfoServiceImpl extends ServiceImpl<ApartmentInfoMapper, ApartmentInfo>
    implements ApartmentInfoService{
    @Autowired
    GraphInfoService graphInfoService;
    @Autowired
    FeeValueService feeValueService;
    @Autowired
    ApartmentFeeValueService apartmentFeeValueService;
    @Autowired
    LabelInfoService labelInfoService;
    @Autowired
    ApartmentLabelService apartmentLabelService;
    @Autowired
    FacilityInfoService facilityInfoService;
    @Autowired
    ApartmentFacilityService apartmentFacilityService;
    @Autowired
    ApartmentInfoMapper apartmentInfoMapper;
    @Autowired
    private ProvinceInfoServiceImpl provinceInfoServiceImpl;
    @Autowired
    private CityInfoServiceImpl cityInfoServiceImpl;
    @Autowired
    private DistrictInfoServiceImpl districtInfoServiceImpl;
    @Autowired
    private RoomInfoService roomInfoService;
    @Override
    public ApartmentDetailVo getDetailById(Long id) {
        ApartmentInfo apartmentInfo = getById(id);
        ApartmentDetailVo apartmentDetailVo = new ApartmentDetailVo();
        BeanUtils.copyProperties(apartmentInfo,apartmentDetailVo);

        // todo : 完善关系表为null逻辑处理
        apartmentDetailVo.setGraphVoList(graphInfoService.listByApartmentId(id));
        List<Long> ids = apartmentFeeValueService.listByApartmentIdLongs(id);
        if(ids!=null && !ids.isEmpty()){
            apartmentDetailVo.setFeeValueVoList(feeValueService.listByProvidedIds(ids));
        }
        List<Long> facilityIds = apartmentFacilityService.listByApartmentId(id);
        if(facilityIds!=null && !facilityIds.isEmpty()){
            apartmentDetailVo.setFacilityInfoList(facilityInfoService.getBaseMapper().selectBatchIds(facilityIds));
        }
        List<Long> labelIds = apartmentLabelService.listByApartmentId(id);
        if(labelIds!=null && !labelIds.isEmpty()){
            apartmentDetailVo.setLabelInfoList(labelInfoService.getBaseMapper().selectBatchIds(labelIds));
        }
        return apartmentDetailVo;
    }

    @Override
    public void saveOrUpdateApartment(ApartmentSubmitVo apartmentSubmitVo) {
        Long id = apartmentSubmitVo.getId();
        boolean isUpdate = id!=null;
        if(isUpdate){
            LambdaQueryWrapper<GraphInfo> graphQueryWrapper = new LambdaQueryWrapper<>();
            graphQueryWrapper.eq(GraphInfo::getItemType, ItemType.APARTMENT);
            graphQueryWrapper.eq(GraphInfo::getItemId, id);
            graphInfoService.remove(graphQueryWrapper);

            LambdaQueryWrapper<ApartmentLabel> apartmentLabelLambdaQueryWrapper = new LambdaQueryWrapper<>();
            apartmentLabelLambdaQueryWrapper.eq(ApartmentLabel::getApartmentId,id);
            apartmentLabelService.remove(apartmentLabelLambdaQueryWrapper);

            LambdaQueryWrapper<ApartmentFacility> apartmentFacilityLambdaQueryWrapper = new LambdaQueryWrapper<>();
            apartmentFacilityLambdaQueryWrapper.eq(ApartmentFacility::getApartmentId,id);
            apartmentFacilityService.remove(apartmentFacilityLambdaQueryWrapper);

            LambdaQueryWrapper<ApartmentFeeValue> apartmentFeeValueLambdaQueryWrapper = new LambdaQueryWrapper<>();
            apartmentFeeValueLambdaQueryWrapper.eq(ApartmentFeeValue::getApartmentId,id);
            apartmentFeeValueService.remove(apartmentFeeValueLambdaQueryWrapper);
        }
        // todo :!null 判定
        //1. save apartment
        ApartmentInfo apartmentInfo = getById(id);
        apartmentInfo.setProvinceName(provinceInfoServiceImpl.getById(apartmentInfo.getProvinceId()).getName());
        apartmentInfo.setCityName(cityInfoServiceImpl.getById(apartmentInfo.getCityId()).getName());
        apartmentInfo.setDistrictName(districtInfoServiceImpl.getById(apartmentInfo.getDistrictId()).getName());
        BeanUtils.copyProperties(apartmentSubmitVo,apartmentInfo);

        saveOrUpdate(apartmentInfo);

        //2. save apartment graph
        List<GraphVo> graphVoList = apartmentSubmitVo.getGraphVoList();
        List<GraphInfo> graphInfos = new ArrayList<>(10);
        for (GraphVo graphVo : graphVoList) {
            GraphInfo graphInfo = new GraphInfo();
            graphInfo.setName(graphVo.getName());
            graphInfo.setUrl(graphVo.getUrl());
            graphInfo.setItemId(apartmentSubmitVo.getId());
            graphInfo.setItemType(ItemType.APARTMENT);
            graphInfos.add(graphInfo);
        }
        graphInfoService.saveBatch(graphInfos);
        //3. save apartment_fee
        List<Long> feeValueList = apartmentSubmitVo.getFeeValueIds();
        List<ApartmentFeeValue> apartmentFeeValues = new ArrayList<>(5);
        for (Long feeValueId : feeValueList) {
            ApartmentFeeValue apartmentFeeValue =  ApartmentFeeValue
                    .builder()
                    .apartmentId(apartmentSubmitVo.getId())
                    .feeValueId(feeValueId)
                    .build();
            apartmentFeeValues.add(apartmentFeeValue);
        }
        apartmentFeeValueService.saveBatch(apartmentFeeValues);
        //4. save apartment_label
        List<Long> labelInfoList = apartmentSubmitVo.getLabelIds();
        List<ApartmentLabel> apartmentLabels = new ArrayList<>(5);
        for (Long labelInfoId : labelInfoList) {
            ApartmentLabel apartmentLabel =  ApartmentLabel
                    .builder()
                    .apartmentId(apartmentSubmitVo.getId())
                    .labelId(labelInfoId)
                    .build();
            apartmentLabels.add(apartmentLabel);
        }
        apartmentLabelService.saveBatch(apartmentLabels);
        //5. save apartment_facility
        List<Long> facilityInfoList = apartmentSubmitVo.getFacilityInfoIds();
        List<ApartmentFacility> apartmentFacilities = new ArrayList<>(5);
        for (Long facilityInfoId : facilityInfoList) {
            ApartmentFacility apartmentFacility =  ApartmentFacility
                    .builder()
                    .apartmentId(apartmentSubmitVo.getId())
                    .facilityId(facilityInfoId)
                    .build();
            apartmentFacilities.add(apartmentFacility);
        }
        apartmentFacilityService.saveBatch(apartmentFacilities);

    }

    @Override
    public IPage<ApartmentItemVo> pageItem(IPage<ApartmentItemVo> page, ApartmentQueryVo apartmentQueryVo) {
        if (apartmentQueryVo.getDistrictId() != null) {
            return apartmentInfoMapper.pageItemDistrictId(page,apartmentQueryVo);
        }
        if (apartmentQueryVo.getCityId() != null) {
            return apartmentInfoMapper.pageItemCityId(page,apartmentQueryVo);
        }
        if (apartmentQueryVo.getProvinceId() != null) {
            return apartmentInfoMapper.pageItemProvinceId(page,apartmentQueryVo);
        }
        //查全部
        return apartmentInfoMapper.pageItem(page,apartmentQueryVo);
    }

    @Override
    public void removeApartmentById(Long id) {
        LambdaQueryWrapper<RoomInfo> roomInfoLambdaQueryWrapper = new LambdaQueryWrapper<>();
        roomInfoLambdaQueryWrapper.eq(RoomInfo::getApartmentId,id);
        long count = roomInfoService.count(roomInfoLambdaQueryWrapper);
        if(count > 0){
            throw new UpException(ResultCodeEnum.DELETE_ERROR);
        }

        LambdaQueryWrapper<GraphInfo> graphQueryWrapper = new LambdaQueryWrapper<>();
        graphQueryWrapper.eq(GraphInfo::getItemType, ItemType.APARTMENT);
        graphQueryWrapper.eq(GraphInfo::getItemId, id);
        graphInfoService.remove(graphQueryWrapper);

        LambdaQueryWrapper<ApartmentLabel> apartmentLabelLambdaQueryWrapper = new LambdaQueryWrapper<>();
        apartmentLabelLambdaQueryWrapper.eq(ApartmentLabel::getApartmentId,id);
        apartmentLabelService.remove(apartmentLabelLambdaQueryWrapper);

        LambdaQueryWrapper<ApartmentFacility> apartmentFacilityLambdaQueryWrapper = new LambdaQueryWrapper<>();
        apartmentFacilityLambdaQueryWrapper.eq(ApartmentFacility::getApartmentId,id);
        apartmentFacilityService.remove(apartmentFacilityLambdaQueryWrapper);

        LambdaQueryWrapper<ApartmentFeeValue> apartmentFeeValueLambdaQueryWrapper = new LambdaQueryWrapper<>();
        apartmentFeeValueLambdaQueryWrapper.eq(ApartmentFeeValue::getApartmentId,id);
        apartmentFeeValueService.remove(apartmentFeeValueLambdaQueryWrapper);

        this.removeById(id);
    }
}




